################################################################################
## zdt1 objectives evaluation function                                        ##
################################################################################
function [obj1, obj2] = zdt1(solution)
    size_of_solution = columns(solution);
    obj1 = solution(1);
    total = 0;
    for i = 2 : size_of_solution
        total = total + solution(i);
    endfor

    g = 1 +  9 * total / (size_of_solution - 1);

    h = 1 - sqrt(obj1 / g);

    obj2 = g * h;
endfunction


################################################################################
## zdt2 objectives evaluation function                                        ##
################################################################################
function [obj1, obj2] = zdt2(solution)
    size_of_solution = columns(solution);
    obj1 = solution(1);

    total = 0;
    for i = 2 : size_of_solution
        total = total + solution(i);
    endfor

    g = 1 +  9 * total / (size_of_solution - 1);

    h = 1 - (obj1 / g)^2;

    obj2 = g * h;
endfunction


################################################################################
## zdt3 objectives evaluation function                                        ##
################################################################################
function [obj1, obj2] = zdt3(solution)
    size_of_solution = columns(solution);
    obj1 = solution(1);

    total = 0;
    for i = 2 : size_of_solution
        total = total + solution(i);
    endfor

    g = 1 +  9 * total / (size_of_solution - 1);

    h = 1 - sqrt(obj1 / g) - (obj1 / g) * sin (10 * pi * obj1);

    obj2 = g * h;
endfunction

################################################################################
## zdt4 objectives evaluation function                                        ##
################################################################################
function [obj1, obj2] = zdt4(solution)
    size_of_solution = columns(solution);
    obj1 = solution(1);

    total = 0;
    for i = 2 : size_of_solution
        total = total + (solution(i)^2 - 10 * cos(4 * pi * solution(i)));
    endfor

    g = 1 +  10 * (size_of_solution - 1) + total;

    h = 1 - sqrt(obj1 / g);

    obj2 = g * h;
endfunction

################################################################################
## zdt5 objectives evaluation function                                        ##
################################################################################
function value = u(solution, variable)
    begin_index = 0;
    end_index = 0;
    if (variable == 1)
        begin_index = 1;
        end_index = 30;
    else
        begin_index = 31 + 5 * (variable -2);
        end_index = 31 + 5 * (variable - 1);
    endif

    value = 0;
    for i = begin_index : end_index
        value = value + solution(i);
    endfor

endfunction

function value = v(solution, variable)

    u_i = u(solution, variable);

    if (u_i == 5)
        value = 1;
    else
        value = u_i + 2;
    endif

endfunction

function [obj1, obj2] = zdt5(solution)

    obj1 = u(solution, 1) + 1;

    g = 0;
    for i = 2 : 11
        g = g + v(solution, i);
    endfor

    obj2 = g / obj1;

endfunction


################################################################################
## zdt6 objectives evaluation function                                        ##
################################################################################
function [obj1, obj2] = zdt6(solution)
    size_of_solution = columns(solution);
    obj1 = 1 - e^(-4 * solution(1)) * (sin(4 * pi * solution(1))^6);

    total = 0;
    for i = 2 : size_of_solution
        total = total + solution(i);
    endfor

    g = 1 +  9 * (total / (size_of_solution - 1))^0.25;

    h = 1 - (obj1 / g)^2;

    obj2 = g * h;
endfunction


################################################################################
## This function creates a set of variables in the pareto front for           ##
## ZDT_i i != 5 obviously                                                     ##
## precision indicates the amount of solutions desired to be generated        ##
################################################################################
function pareto_front_solutions = generate_pareto_front_solutions(precision,
                                                                solution_size)
    pareto_front_solutions = zeros(precision, solution_size);
    for i = 1 : precision
        pareto_front_solutions(i, 1) = (i - 1) / precision;
    endfor
endfunction

function pareto_front = pareto_front_zdt5(solution_size)
    front_size = 31;
    pareto_front = zeros(31, 2);
    for i = 1 : 31
        pareto_front(i, 1) = i;
        pareto_front(i, 2) = 10/i;
    endfor
endfunction




################################################################################
## generates the real pareto front                                            ##
################################################################################
function pareto_front = generate_pareto_front(precision, solution_size, problem)
    solution_size

    if (strcmp(problem, "ZDT5") != 1)
        solutions = generate_pareto_front_solutions(precision, solution_size);
        pareto_front = zeros(precision, 2);
    endif

    if (strcmp(problem,"ZDT1") == 1)
        for i = 1 : precision
            [pareto_front(i, 1), pareto_front(i,2)] = zdt1(solutions(i,:));
        endfor
    elseif (strcmp(problem,"ZDT2") == 1)
        for i = 1 : precision
            [pareto_front(i, 1), pareto_front(i,2)] = zdt2(solutions(i,:));
        endfor
    elseif (strcmp(problem,"ZDT3") == 1)
        for i = 1 : precision
            [pareto_front(i, 1), pareto_front(i,2)] = zdt3(solutions(i,:));
        endfor
    elseif (strcmp(problem,"ZDT4") == 1)
        for i = 1 : precision
            [pareto_front(i, 1), pareto_front(i,2)] = zdt4(solutions(i,:));
        endfor
    elseif (strcmp(problem,"ZDT5") == 1)
        for i = 1 : precision
            pareto_front = pareto_front_zdt5(solution_size);
        endfor
    elseif (strcmp(problem,"ZDT6") == 1)
        for i = 1 : precision
            [pareto_front(i, 1), pareto_front(i,2)] = zdt6(solutions(i,:));
        endfor
    else
            fprintf(stderr, "\n*****problem %s unknown, aborting\n", problem);
    endif
endfunction

